package com.gitee.hermer.boot.jee.io.auto.configuration;

import org.apache.activemq.ActiveMQConnectionFactory;
import org.apache.activemq.pool.PooledConnectionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.stereotype.Component;

import com.corundumstudio.socketio.AuthorizationListener;
import com.corundumstudio.socketio.HandshakeData;
import com.corundumstudio.socketio.SocketIOServer;
import com.gitee.hermer.boot.jee.commons.annotation.ConditionalOnLikeProperty;
import com.gitee.hermer.boot.jee.commons.collection.CollectionUtils;
import com.gitee.hermer.boot.jee.commons.log.UtilsContext;
import com.gitee.hermer.boot.jee.commons.number.IntegerUtils;
import com.gitee.hermer.boot.jee.commons.reflect.ClassUtils;
import com.gitee.hermer.boot.jee.commons.utils.StringUtils;
import com.gitee.hermer.boot.jee.io.activemq.ActiveMQExecute;
import com.gitee.hermer.boot.jee.io.properties.IOActiveMQProperties;
import com.gitee.hermer.boot.jee.io.properties.IOSocketProperties;
import com.gitee.hermer.boot.jee.io.socket.SocketIOEventHandler;

@Configuration                                                                                                                              
@EnableConfigurationProperties(value = {IOActiveMQProperties.class,IOSocketProperties.class})                                                                        
@ConditionalOnClass(value={ActiveMQExecute.class,PooledConnectionFactory.class})                                                                                                     
@ConditionalOnProperty(prefix = "com.boot.jee.io", value = "enable",havingValue="true",matchIfMissing = false)    
public class IOAutoConfiguration extends UtilsContext{

	@Autowired
	private IOActiveMQProperties activeMQProperties;
	@Autowired
	private IOSocketProperties socketProperties;


	@Bean(destroyMethod="stop")
	@ConditionalOnLikeProperty(prefix = "com.boot.jee.io",value = "factory", likeValue = "activemq", matchIfMissing = false)  
	public  PooledConnectionFactory getConnectionFactory(){
		PooledConnectionFactory connectionFactoryBean = null;
		try {
			String brokerURL = activeMQProperties.getUrl();
			String userName = activeMQProperties.getUserName();
			String passWord = activeMQProperties.getPassWord();
			ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory(userName, passWord, brokerURL);
			connectionFactoryBean = new PooledConnectionFactory();	
			connectionFactoryBean.setConnectionFactory(connectionFactory);
			connectionFactoryBean.setMaxConnections(2000);
		} catch (Exception e) {
			error(e.getMessage(),e);
		}
		return connectionFactoryBean;
	}


	@Bean()
	@ConditionalOnLikeProperty(prefix = "com.boot.jee.io",value = "factory", likeValue = "activemq", matchIfMissing = false)  
	public  ActiveMQExecute getActiveMQExecute(){
		ActiveMQExecute execute = new ActiveMQExecute();
		return execute;

	}

	@Bean(destroyMethod="stop",initMethod="start")
	@ConditionalOnLikeProperty(prefix = "com.boot.jee.io",value = "factory", likeValue = "socketio", matchIfMissing = false)  
	@ConditionalOnMissingBean(SocketIOServer.class)
	public  SocketIOServer getSocketIOServer(SocketIOEventHandler[] handlers){
		com.corundumstudio.socketio.Configuration config = new com.corundumstudio.socketio.Configuration();  
		config.setHostname(socketProperties.getHost());  
		config.setPort(IntegerUtils.defaultIfError(socketProperties.getPort(), 1000));  
		config.setAuthorizationListener(new AuthorizationListener() {

			@Override
			public boolean isAuthorized(HandshakeData data) {
				return true;
			}  
			
		});
		final SocketIOServer server = new SocketIOServer(config);  
		if(CollectionUtils.isNotEmpty(handlers)){
			for (SocketIOEventHandler socketIOEventHandler : handlers) {
				Component component = ClassUtils.getClassAnnotation(socketIOEventHandler.getClass(), Component.class);
				if(StringUtils.isNotEmpty(component.value()))
					server.addNamespace(component.value()).addListeners(socketIOEventHandler);
			}
		}
		
		return server;
	}


}
